Шаг 3. Решаем конфликт с помощью командной строки
Для начала создадим новую ветку. В этом раз мы будем использовать модель ветвления TBD (Trunk Based Development). Здесь под каждую задачу есть своя ветка. Выполнил задачу — удалил ветку.
TBD — модель ветвления, при которой ветки живут недолго, обычно удаляются после слияния с основной веткой.
Новую ветку назовём conflict/command-line. Создаём её с помощью команды git switch --create conflict/command-line.
Далее вносим изменение: для элемента <h1> установим атрибут class со значением title.
Добавим это изменение в индекс с помощью команды git add --all, а затем зафиксируем его — git commit --message "feat: added the class attribute with the title value for the h1 element".
Теперь перейдём на ветку main с помощью команды gti switch main.
Далее точно так же для элемента <h1> добавим атрибут class, но с другим значением — subheading. Мы специально написали неправильный класс, чтобы можно было заменить на правильный.
Затем добавим это изменение в индекс с помощью команды git add --all, а после зафиксируем с помощью команды git commit --message "feat: added the class attribute with the subheading value for the h1 element".
Далее выполним слияния. Пропишем команду git merge conflict/command-line --no-ff --message "feat: the conflict/command-line branch was merged into the main branch". Слияние будем выполнять с использованием режима no-fast-forward, чтобы создался коммит слияния.
Переходим к решению конфликта.
У нас есть выбор: оставить класс, который был на ветке main, или выбрать класс, который мы добавили на ветке conflict/command-line.
Если вы хотите выбрать изменение, пришедшее с conflict/command-line, воспользуйтесь командой git checkout --their index.html. Если хотите выбрать изменение, которое было на ветке main, используйте команду git checkout --ours index.html.
Опция --their отвечает за входящие изменения, а опция --ours — за принятие изменений, которые были сделаны в текущей (целевой) ветке.
Вместо файла index.html может быть любой другой файл, в котором возник конфликт. Минус этого подхода в том, что если у вас конфликт в нескольких местах, то с помощью этих команд вы не сможете выбрать разные значения для разных участков кода. То есть у вас либо примутся все входящие изменения, либо все те, которые были в текущей ветке.
Если же вам нужно в одном месте принять входящие изменения, а в другом оставить текущие, придётся вручную менять файл. Собственно, как мы это делали в демонстрации, когда затягивали изменение с удалённого репозитория.
Мы выберем входящие изменения. Поэтому воспользуемся командой git checkout --their index.html.
Конфликт решён.
Теперь давайте проверим статус файла с помощью команды git status.
index.html находится в разделе Unmerged paths, что означает «Не слитые (не замкнутые) пути», а также имеет статус both modified — «Оба модифицированные».
Почему оба, если файл один? Git учитывает не только файл на ветке main, но и на ветке conflict/command-line. Пока мы не добавим данное изменение в индекс и не зафиксируем, он будет считать оба файла модифицированными.
Давайте добавим изменение в индекс с помощью команды git add --all.
Теперь у нас есть два варианта развития событий.
- Мы можем самостоятельно создать коммит с помощью команды
git commit --message "текст коммита". - Мы воспользуемся командой
git merge --continue. Она позволяет продолжить слияние, поэтому у нас будет создан коммит с текстом, который мы указывали, когда прописывали команду слияния.
Мы выбираем второй вариант. Пропишем команду git merge --continue. Тут нужно упомянуть: если слияние проходит с использованием режима fast-forward, то вам придётся вручную создавать коммит.
Открылся специальный файл Git — COMMIT_EDITMSG, который позволяет отредактировать текст коммита. Текст коммита нам редактировать не нужно. Поэтому, находясь в файле, просто нажмём сочетание клавиш Ctrl + S, чтобы сохранить изменения, а затем закроем его.
Внизу в этом файле также отмечен наш модифицированный index.html. После его закрытия вернёмся в Git Bash и увидим, что коммит создан.
Далее отправим изменение в удалённый репозиторий с помощью команды git push.
Изменения отправлены. Теперь мы можем удалить временную ветку conflict/command-line. Для этого воспользуемся командой git branch --delete conflict/command-line.
Напоследок посмотрим список всех коммитов и убедимся, что изменения дошли до удалённого репозитория. Для этого пропишем команду git log --oneline.
Сейчас изменения находятся в удалённом репозитории. Также в истории мы можем видеть тот самый коммит, который был сначала извлечён из ветки conflict/command-line, а затем применён к ветке main.